#include "Character.h"

Character::Character(istream& input, SpellSet& spellSet) : spellSet(spellSet) {
	input >> _hpMax >> _mpMax;
	input >> _attack >> _defence >> _range;
	_hp = _hpMax; _mp = _mpMax;

	input >> _actionPointMax;
	_actionPoint = _actionPointMax;
}

Character::Character(Character& c)
	: _hp(c._hp), _mp(c._mp), _hpMax(c._hpMax), _mpMax(c._mpMax),
	_attack(c._attack), _defence(c._defence), _range(c._range),
	_actionPoint(c._actionPoint), _actionPointMax(c._actionPointMax),
	spellSet(c.spellSet) {
}

Character::Character()
	: _hp(5), _mp(0), _hpMax(5), _mpMax(0), _attack(1), _defence(0), _range(1),
	_actionPoint(1), _actionPointMax(1), spellSet(SpellSet()) {

}

bool Character::checkDead() {
	return _hp <= 0;
}

void Character::fillActionPoint() {
	_actionPoint = _actionPointMax;
}

void Character::castSpellOn(Spell& spell, Character& character) { //TODO called from higher level to solve AOE/Global thing.
	auto currentEffects = character.currentEffects;
	auto effectList = spell.effect;

	for (auto effect : effectList) {
		currentEffects.push_back(EffectOnCharacter(*this, effect));
	}

	_actionPoint -= spell.actionPoint;
}

bool Character::updateEffect(EffectOnCharacter& effectOnCharacter) {
	if (effectOnCharacter.delay == 0) {
		
		const Character& caster = effectOnCharacter.caster;
		const EffectSingle& effect = effectOnCharacter.effect;

		if(effect.type == EffectWeapon) {
			_hp -= caster.attack - _defence;
		}

		_hp += effect.hp;
		_mp += effect.mp;
		_hpMax += effect.hpMax;
		_mpMax += effect.mpMax;
		_attack += effect.attack;
		_defence += effect.defence;
		_range += effect.range;

		checkDead();
		return (--effectOnCharacter.duration == 0);

	} else {
		effectOnCharacter.delay--;
		return false;
	}
}

void Character::updateEffects() {
	for (auto i = currentEffects.begin(); i != currentEffects.end();) {
		if (updateEffect(*i)) {
			i = currentEffects.erase(i);
		} else {
			i++;
		}
	}
}
